AWS Lambda Function URLsをServerless Frameworkで使ってみた
はじめに
こんにちは、サービスグロースチームの筧です。
AWS Lambda Function URLsという、熱いアップデートがきましたね。
- AWS Lambda Function URLs: built-in HTTPS endpoints for your Lambda functions
- Announcing AWS Lambda Function URLs: Built-in HTTPS Endpoints for Single-Function Microservices | Amazon Web Services
Serverless Framworkはいつ頃対応するかなとか思いつつ、Serverless FrameworkのNewsを確認すると、、
爆速で対応しているやんけー!!ということで、本ブログではServerless FrameworkでAWS Lambda Function URLsを使う方法を見ていきます。
AWS Lambda Function URLsとは?
A Lambda Function URL is a simple solution to create HTTP endpoints with AWS Lambda. Function URLs are ideal for getting started with AWS Lambda, or for single-function applications like webhooks or APIs built with web frameworks.
While not a complete replacement for API Gateway, which provides more features, a Function URL is a simpler alternative with no extra cost and a much larger timeout limit. We will explore the pros and cons in detail in this article.
引用:AWS Lambda Function URLs with Serverless Framework
Serverless FrameworkのNewsの記載によれば、AWS Lambda Function URLs(以降、Function URLs)は、以下のような機能のようです。
- AWS Lambdaを使用してHTTPエンドポイントを作成する機能
- AWS Lambdaの使用を開始する場合や、WebhookやWebフレームワークで構築されたAPIなどの単一機能アプリケーションに最適
- より多くの機能を提供するAPIGatewayの完全な代替ではないが、追加コストがなく、タイムアウト制限がはるかに大きい、より単純な代替手段
引用元サイトでは、API Gatewayとの違いやユースケースについても記載があるので、よかったら参照ください。
使ってみた
それではServerless FrameworkでFunction URLsを使ってみましょう!
前提
To use that new feature, upgrade Serverless Framework (v3.12.0 or greater).
Serverless FrameworkでFunction URLsを利用するためには、Serverless Frameworkのバージョンをv3.12.0以上にします。
"dependencies": { "serverless": "^3.12.0" },
今回の検証には、以下のようなレスポンスを返すLambdaをServerless Frameworkを使っていきます。
$ sls invoke local -f hello --stage dev { "statusCode": 200, "body": "{\"message\": \"Serverless Framework support is very fast!\"}" }
import json def hello(event, context): body = { "message": "Serverless Framework support is very fast!", } response = {"statusCode": 200, "body": json.dumps(body)} return response
Function URLsを利用するには?
以下はserverless.ymlのfunctions部分です。
functions: hello: handler: src/handlers/handler.hello
現状は下図のようにURLは発行されていません。
以下のように、urlプロパティを追加するだけで、Function URLsを利用して、URLが発行できます。
functions: hello: handler: src/handlers/handler.hello url: true
urlプロパティを追加した状態でデプロイすると、URLが発行されました!「endpoint:」の後にURLが表示されています!(書いているURLはダミーです)また、AWSコンソール側も問題なく表示されていますね。
$ sls deploy --stage dev Running "serverless" from node_modules Deploying blog-lambda-function-urls to stage dev (ap-northeast-1) ✔ Pruning of functions complete ✔ Service deployed to stack blog-lambda-function-urls-dev (67s) endpoint: https://xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.lambda-url.ap-northeast-1.on.aws/ functions: hello: blog-lambda-function-urls-dev-hello (10 MB) 1 deprecation found: run 'serverless doctor' for more details Toggle on monitoring with the Serverless Dashboard: run "serverless"
URLにリクエストを投げてみると、ちゃんとレスポンスが返ってきました。
$ curl "https://xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.lambda-url.ap-northeast-1.on.aws/" -X POST {"message": "Serverless Framework support is very fast!"}
IAM認証による保護
serverless.ymlでauthorizerを記述することで、IAM認証による保護ができます。
functions: hello: handler: src/handlers/handler.hello url: authorizer: aws_iam
認証せずURLにリクエストを行うと、拒否されました。
$ curl "https://xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.lambda-url.ap-northeast-1.on.aws/" -X POST {"Message":"Forbidden"}
認証してURLリクエストを送ってみます。IAM認証情報はaws-vault
で渡して、AWS署名バージョン4リクエスト署名を備えたcurlのようなツールであるawscurl
でリクエストを行うと、ちゃんとレスポンスが返ってきました。
$ aws-vault exec {プロファイル名} -- awscurl --service lambda \ --region ap-northeast-1 \ https://xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx.lambda-url.ap-northeast-1.on.aws {"message": "Serverless Framework support is very fast!"}
CORSを構成する
serverless.ymlでcorsを記述することで、CORSを構成することができます。設定値は以下のページの例を参照しています。
functions: hello: handler: src/handlers/handler.hello url: cors: allowCredentials: true allowedHeaders: - Content-Type - Authorization allowedMethods: - GET allowedOrigins: - https://url1.com - https://url2.com exposedResponseHeaders: - Special-Response-Header maxAge: 6000
AWSコンソール側に問題なく設定が反映されています。
おわりに
最後まで読んでいただきありがとうございます。
Serverless Frameworkでも簡単にFunction URLsを利用できましたね。Function URLs自体の詳細については、後述のブログを是非参照してみてください。
それではまた!